package sg.edu.nus.iss.vmcs.customer;

import java.awt.Button;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.awt.event.WindowListener;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;


import sg.edu.nus.iss.vmcs.abstraction.ICustomerPanel;
import sg.edu.nus.iss.vmcs.abstraction.IStoreService;
import sg.edu.nus.iss.vmcs.abstraction.ITransactionListener;
import sg.edu.nus.iss.vmcs.abstraction.ITransactionService;
import sg.edu.nus.iss.vmcs.abstraction.Messages;
import sg.edu.nus.iss.vmcs.abstraction.PresenterBase;
import sg.edu.nus.iss.vmcs.store.DrinksBrand;
import sg.edu.nus.iss.vmcs.store.Store;
import sg.edu.nus.iss.vmcs.store.StoreItem;
import sg.edu.nus.iss.vmcs.system.ServiceRepository;

/*
 * @author nyi nyi than
 */
public class CustomerPanelPresenter extends PresenterBase<ICustomerPanel>
{
    WindowListener closingListener;
    ActionListener coinInsertListener;
    ActionListener drinkSelectListener;
    ActionListener terminateListener;
    
    IStoreService storeService;
    ITransactionService transactionService;
    String selectedItem = "";
    public CustomerPanelPresenter(String name)
    {
	super(name);
	PresenterBase.mediator.register(this);
	storeService = ServiceRepository.GetInstance().getService(
		IStoreService.class);

	transactionService = ServiceRepository.GetInstance().getService(
		ITransactionService.class);
	
	
	initializeListeners();
    }

    private void initializeListeners()
    {
	this.closingListener = new WindowAdapter()
	{
	    public void windowClosing(WindowEvent e)
	    {
		closeDown();
	    }
	};

	this.coinInsertListener = new ActionListener()
	{
	    public void actionPerformed(ActionEvent event)
	    {
		int totalMoney = 0;
		
		Button btn = (Button) event.getSource();
		if (btn.getLabel().equalsIgnoreCase("invalid"))
		{
		    view.showInvalidCoinStatus();
		    return;
		}
		
		view.hideInvalidCoinStatus();

		
		if(btn.getLabel().contains("50C")){
		    totalMoney = 50;
		}
		else if(btn.getLabel().contains("10C")){
		    totalMoney = 10;
		}
		else if(btn.getLabel().contains("20C")){
		    totalMoney = 20;
		}
		else if(btn.getLabel().contains("5C")){
		    totalMoney = 5;
		}
		else if(btn.getLabel().contains("1")){
		    totalMoney = 100;
		}
		
				
		view.setTotalMoneyInserted(totalMoney);
			
		transactionService.processMoneyReceived(totalMoney);
		
	    }
	};

	this.drinkSelectListener = new ActionListener()
	{
	    public void actionPerformed(ActionEvent event)
	    {
		selectedItem = ((Button) event
			.getSource()).getLabel();
		view.setDrinkSelectionBoxStatus(false, selectedItem);
		view.setCoinInputBoxStatus(true);
		view.setCoinCollectionLabel("");
		view.setCanCollectionLabel("");
		transactionService.startTransaction(selectedItem,view.getSelectedItemPrice(selectedItem));		
	    }
	};
	
	this.terminateListener = new ActionListener()
	{
	    public void actionPerformed(ActionEvent event)
	    {
		view.reset();
		transactionService.terminateTransaction();
	    }
	};
	
	this.transactionService.registerTransactionCompletedListener(
		new ITransactionListener()
		{
		    @Override
		    public void TransactionCompleted(int refundCoins)			    
		    {
			view.reset();		
			if(refundCoins > 0)
			{
			    view.setCoinCollectionLabel(String.valueOf(refundCoins));
			}
			transactionService.dispense();
			view.dispense(selectedItem);
		    }	    
		});
	
    }

    @Override
    public void closeDown()
    {
	this.view.closeDown();
    }

    @Override
    public void display()
    {
	this.view.display();
    }

    @Override
    public void notify(PresenterBase<?> sender, String message)
    {
	if (Messages.OPEN.equalsIgnoreCase(message))
	{
	    display();
	} else if (Messages.CLOSE.equalsIgnoreCase(message))
	{
	    closeDown();
	} else if (Messages.REFRESH.equalsIgnoreCase(message))
	{
	    view.refresh();
	}
    }

    @Override
    public void send(String receiverName, String message)
    {
	mediator.sendMessage(this, receiverName, message);
    }

    public WindowListener getClosingListener()
    {
	return this.closingListener;
    }

    public ActionListener getTerminateListener()
    {
	return this.terminateListener;
    }
    
    public ActionListener getCoinInputListener()
    {
	return this.coinInsertListener;
    }

    public ActionListener getDrinkSelectListener()
    {
	return this.drinkSelectListener;
    }

    public ArrayList<DrinkSelectionItem> getDrinkSelectionItems()
    {

	ArrayList<DrinkSelectionItem> drinkSelectionItems = new ArrayList<DrinkSelectionItem>();
	StoreItem[] items = storeService.getStoreItems(Store.DRINK);
	ArrayList<StoreItem> distinctItems = getDistinct(items);
	for (StoreItem item : distinctItems)
	{

	    DrinksBrand brand = (DrinksBrand) item.getContent();
	    String price = brand.getPrice() >= 100 ? "$ "
		    + Double.toString(brand.getPrice() / 100.0) : Integer
		    .toString(brand.getPrice())
		    + " C";
	    DrinkSelectionItem drinkItem = new DrinkSelectionItem(brand
		    .getName(), price, item.getQuantity(), this
		    .getDrinkSelectListener());
	    drinkSelectionItems.add(drinkItem);
	}

	return drinkSelectionItems;
    }

    @SuppressWarnings("unchecked")
    private ArrayList<StoreItem> getDistinct(StoreItem[] items)
    {
	ArrayList<StoreItem> distinctItems = new ArrayList<StoreItem>();

	Set set = new HashSet();

	for (StoreItem item : items)
	{
	    if (!set.contains(item))
	    {
		set.add(item);
	    }
	}

	Iterator itr = set.iterator();
	while (itr.hasNext())
	{
	    distinctItems.add((StoreItem) itr.next());
	}

	return distinctItems;
    }
}
